/*
*ClassName:TMessage
*Description:全局消息
*Date:2019/10/7 15:39
*/

import UIBaseView, {UIClass} from "./view/UIBaseView";
export default class TMessage {

    protected static className;
    public static getName(): string {
        return this.className;
    }

    private static _handlers: any = {}; //注册事件的列表

    public static RegisterListener(messageName: string, callBack: Function, target: Object, once: boolean = false) {
        if (callBack == null) {
            console.error("Failed to add Message Listener because the given callback is null!");
            return;
        }

        !this._handlers[messageName] && (this._handlers[messageName] = []);
        if (this.HasHandler(messageName, callBack)) return;
        this._handlers[messageName].push({
            callBack,
            target,
            once
        });
    }

    /**注销事件*/
    private static UnregisterListener(messageName: string, callBack: Function, target: Object) {
        //console.log("-->RemoveNotifyDelegate:{0} => target:{1} method:{2}", messageName, callback.Target, callback.Method);
        if (!this._handlers[messageName] || this._handlers[messageName].length == 0)
            return;
        this._handlers[messageName].forEach((element: { callBack: Function, target }, index) => {
            if (element.callBack == callBack && element.target == target) {
                this._handlers[messageName].splice(index, 1);
            }
        })
    }

    /// <summary>
    /// 添加监听
    /// </summary>
    /// <typeparam message="T">消息类型</typeparam>
    /// <param callback="Function">回调函数</param>
    /// <param target="Object">回调函数</param>
    /// <param once="boolean">回调函数</param>
    public static AddListener<T extends BaseEventMessage>(message: BaseTMessage<T>, callback: Function, target: Object, once: boolean = false) {
        this.RegisterListener(message.getName(),callback, target, once);
    }

    /// <summary>
    /// 删除监听
    /// </summary>
    /// <param name="messageName">消息名称</param>
    /// <param name="callback">回调函数</param>
    public static RemoveListener<T extends BaseEventMessage>(message: BaseTMessage<T>, callback: Function, target: Object) {
        this.UnregisterListener(message.getName(), callback, target);
    }

    /**移除某个消息的的所有的事件监听*/
    public static RemoveAllListeners<T>(messageName: string) {
        if (!this._handlers[messageName] || this._handlers[messageName].length == 0) {
            console.warn("eventType not registered：" + messageName);
            return;
        }
        //console.log("-->RemoveNotifyDele:" + message.name);
        this._handlers[messageName] = [];
    }

    public static NotifyMessage<T>(message: BaseTMessage<T>, messageBase: BaseEventMessage = null, inQueue: boolean = false) {
        if (inQueue)
            console.error("Failed to add Message Listener because the given callback is null!");
        else {
            //console.log("Notify msg name = ",message.getName())
            this.Notify(message.getName(), messageBase);
        }
    }

    public static Notify(messageName: string, message: Object = null) {
        if (!this._handlers[messageName] || this._handlers[messageName].length == 0) {
            console.warn("eventType not registered：" + messageName);
            return;
        }
        this._handlers[messageName].forEach(obj => {
            obj.callBack && obj.callBack.call(obj.target, message);
            obj.once && this.UnregisterListener(messageName, obj.callBack, obj.target);
        });
    }

    //打开UIView
    public static NotifyShowUI<T extends UIBaseView>(uiClass:UIClass<T>,msg:BaseEventMessage = null,onProgress = null, onComplete = null){
        let msgLister: UIViewPanelShowMsg = new UIViewPanelShowMsg();
        msgLister.uiClass = uiClass;
        msgLister.msg = msg;
        msgLister.onProgress = onProgress;
        msgLister.onComplete = onComplete;
        TMessage.NotifyMessage(UIViewPanelShowMsg,msgLister);
    }

    //打开UIScene
    public static NotifyShowScene<T extends UIBaseView>(uiClass:UIClass<T>,msg:BaseEventMessage = null,onProgress = null, onComplete = null){
        let msgLister: UIViewSceneShowMsg = new UIViewSceneShowMsg();
        msgLister.uiClass = uiClass;
        msgLister.msg = msg;
        msgLister.onProgress = onProgress;
        msgLister.onComplete = onComplete;
        TMessage.NotifyMessage(UIViewSceneShowMsg,msgLister);
    }

    //打开UIView
    public static NotifyLoadingUI(prefabPath:string,msg:BaseEventMessage = null,onProgress = null, onComplete = null){
        let msgLister: UIViewPanelLoadingMsg = new UIViewPanelLoadingMsg();
        msgLister.prefabPath = prefabPath;
        msgLister.msg = msg;
        msgLister.onProgress = onProgress;
        msgLister.onComplete = onComplete;
        TMessage.NotifyMessage(UIViewPanelLoadingMsg,msgLister);
    }

    //打开UIScene
    public static NotifyLoadingScene(prefabPath:string,msg:BaseEventMessage = null,onProgress = null, onComplete = null){
        let msgLister: UIViewSceneLoadingMsg = new UIViewSceneLoadingMsg();
        msgLister.prefabPath = prefabPath;
        msgLister.msg = msg;
        msgLister.onProgress = onProgress;
        msgLister.onComplete = onComplete;
        TMessage.NotifyMessage(UIViewSceneLoadingMsg,msgLister);
    }


    /**是否存在事件*/
    private static HasHandler(messageName: string, callBack: Function): boolean {
        return this._handlers[messageName].some(element => {
            if (element.callBack == callBack) return true;
        })
    }

    public static OnSetHash(str: string): string {
        let hash = 0;
        if (str.length == 0) return hash.toString();
        for (let i = 0; i < str.length; i++) {
            var char = str.charCodeAt(i);
            hash = ((hash << 5) - hash) + char;
            hash = hash & hash;
        }
        return hash.toString();
    }

}



export class BaseEventMessage extends TMessage {


    // public  SendMsg<T>()  : BaseMessage
    // {
    //     //ATrace.Log("Simple_Msg:" + typeof(T).ToString());
    //     TMessage.Notify<T>((T)this);
    // }
    //
    // public static Send<T>()  : BaseMessage
    // {
    //     T inst = Activator.CreateInstance<T>();
    //     inst.SendMsg<T>();
    // }
}

export interface BaseTMessage<T extends BaseEventMessage> {
    new(): T;
    getName(): string;
}
//--------------------------------UI------------------------
//显示所有view
export class UIViewPanelShowMsg extends BaseEventMessage{
    protected static className = "UIViewPanelShowMsg";

    public uiClass: any = null;
    public msg:BaseEventMessage = null;
    public onProgress:any = null;
    public onComplete:any = null;
}

//loading view
export class UIViewPanelLoadingMsg extends BaseEventMessage{
    protected static className = "UIViewPanelLoadingMsg";

    public prefabPath: string = null;
    public msg:BaseEventMessage = null;
    public onProgress:any = null;
    public onComplete:any = null;
    public isShow:boolean = false;
}

/****隐藏所有的UI*/
export class UIViewPanelHideAllMsg extends BaseEventMessage{
    protected static className = "UIViewPanelHideAllMsg";
}
//---------------------scene------------------------------
//显示所有scene
export class UIViewSceneShowMsg extends BaseEventMessage{
    protected static className = "UIViewSceneShowMsg";

    public uiClass:any = null;
    public msg:BaseEventMessage = null;
    public onProgress:any = null;
    public onComplete:any = null;
}

//显示所有view
export class UIViewSceneLoadingMsg extends BaseEventMessage{
    protected static className = "UIViewSceneLoadingMsg";

    public prefabPath: string = null;
    public msg:BaseEventMessage = null;
    public onProgress:any = null;
    public onComplete:any = null;
    public isShow:boolean = false;
}




